package com.yyks.cnbooking.dubbo.controller;

import cn.hutool.core.date.DatePattern;
import cn.hutool.core.date.DateUtil;
import com.yeyks.common.ajax.AjaxResponseBody;
import com.yeyks.common.utils.DateUtils;
import com.yyks.cnbooking.dubbo.base.CNResponse;
import com.yyks.cnbooking.dubbo.dto.hotel.HotelInfoDTO;
import com.yyks.cnbooking.dubbo.param.CbPreBookingCheckParam;
import com.yyks.cnbooking.dubbo.param.addresssearch.CbAddressSearchParam;
import com.yyks.cnbooking.dubbo.param.booking.CbBookInfo;
import com.yyks.cnbooking.dubbo.param.booking.CbBookingParam;
import com.yyks.cnbooking.dubbo.param.booking.CbGuestInfo;
import com.yyks.cnbooking.dubbo.param.booking.CbGuestInfos;
import com.yyks.cnbooking.dubbo.param.hotel.CbHotelListSearchParam;
import com.yyks.cnbooking.dubbo.param.hotel.CbHotelListSearchStayDateRange;
import com.yyks.cnbooking.dubbo.param.hotel.CbHotelSearchParam;
import com.yyks.cnbooking.dubbo.param.ordersearch.CbOrderSearchParam;
import com.yyks.cnbooking.dubbo.param.rateplansearch.CbRatePlanSearchParam;
import com.yyks.cnbooking.dubbo.param.roomsearch.CbRoomSearchParam;
import com.yyks.cnbooking.dubbo.result.addresssearch.CbAddressSearchData;
import com.yyks.cnbooking.dubbo.result.booking.CbBookingData;
import com.yyks.cnbooking.dubbo.result.hotellistsearch.CbHotelListSearchData;
import com.yyks.cnbooking.dubbo.result.hotelsearch.CbHotelSearchData;
import com.yyks.cnbooking.dubbo.result.ordersearch.CbOrderSearchData;
import com.yyks.cnbooking.dubbo.result.prebookingcheck.CbPreBookingCheckData;
import com.yyks.cnbooking.dubbo.result.rateplansearch.CbRatePlanSearchData;
import com.yyks.cnbooking.dubbo.result.roomsearch.CbRoomSearchData;
import com.yyks.cnbooking.dubbo.service.CNBookingService;
import com.yyks.cnbooking.dubbo.service.TransitionService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.apache.commons.lang.StringUtils;
import org.apache.dubbo.config.annotation.Reference;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import javax.validation.Valid;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

@RestController
@Api(tags = "CNBooking服务接口类")
@RequestMapping("/cn/booking")
public class CNBookingController {

    @Reference(protocol = "dubbo")
    private CNBookingService cnBookingService;
    @Reference(protocol = "dubbo")
    private TransitionService transitionService;


    @ApiOperation("CNBooking酒店搜索")
    @GetMapping("/hotelSearch")
    public AjaxResponseBody hotelSearch(String countryId,
                                        String hotelId,
                                        String provinceId,
                                        String cityId,
                                        Integer pageSize,
                                        Integer pageNo) {
        CbHotelSearchParam hotelSearchParam = new CbHotelSearchParam();
        hotelSearchParam.setCountryId(countryId);
        hotelSearchParam.setHotelId(hotelId);
        hotelSearchParam.setProvinceId(provinceId);
        hotelSearchParam.setCityId(cityId);
        hotelSearchParam.setPageSize(pageSize);
        hotelSearchParam.setPageNo(pageNo);
        CNResponse<CbHotelSearchData> cnResponse = cnBookingService.hotelSearch(hotelSearchParam);
        return AjaxResponseBody.success(cnResponse);
    }

    @ApiOperation(value = "CNBooking酒店搜索返回酒店对象", response = HotelInfoDTO.class)
    @GetMapping("/hotelSearch/return/hotelInfo")
    public AjaxResponseBody hotelSearchReturnHotelInfo(String countryId,
                                                       String hotelId) {
        HotelInfoDTO hotelInfoDTO = transitionService.hotelSearch(countryId, hotelId);
        return AjaxResponseBody.success(hotelInfoDTO);
    }

    @ApiOperation("CNBooking酒店列表搜索")
    @GetMapping("/hotelListSearch")
    public AjaxResponseBody hotelListSearch(Integer pageSize,
                                            Integer pageNo) {
        CbHotelListSearchParam hotelSearchParam = getCbHotelListSearchParam();
        hotelSearchParam.setPageSize(pageSize);
        hotelSearchParam.setPageNo(pageNo);
        CNResponse<CbHotelListSearchData> cnResponse = cnBookingService.hotelListSearch(hotelSearchParam);
        return AjaxResponseBody.success(cnResponse);
    }

    @ApiOperation("CNBooking酒店列表搜索返回酒店对象")
    @GetMapping("/hotelListSearch/return/hotelInfo")
    public AjaxResponseBody hotelListSearchReturnHotelInfo(Integer pageSize,
                                                           Integer pageNo) {
        CbHotelListSearchParam hotelSearchParam = getCbHotelListSearchParam();
        hotelSearchParam.setPageSize(pageSize);
        hotelSearchParam.setPageNo(pageNo);
        List<HotelInfoDTO> hotelInfoDTOS = transitionService.hotelListSearch(hotelSearchParam);
        return AjaxResponseBody.success(hotelInfoDTOS);
    }


    @ApiOperation("CNBooking预订下单前校验")
    @PostMapping("/preBookingCheck")
    public AjaxResponseBody preBookingCheck(String hotelId,
                                            String roomId,
                                            String ratePlanId,
                                            String checkIn,
                                            String checkOut,
                                            String roomCount,
                                            @ApiParam(name = "currency", allowableValues = "CNY")
                                            String currency,
                                            String orderAmount) {
//        cbPreBookingCheckParam.setHotelId("82205");
//        cbPreBookingCheckParam.setRoomId("227408");
//        cbPreBookingCheckParam.setRateplanId("1205");
//        cbPreBookingCheckParam.setCheckIn("2019-10-19");
//        cbPreBookingCheckParam.setCheckOut("2019-10-20");
//        cbPreBookingCheckParam.setRoomCount("1");
//        cbPreBookingCheckParam.setCurrency("CNY");
//        cbPreBookingCheckParam.setOrderAmount("665");
        CbPreBookingCheckParam cbPreBookingCheckParam = new CbPreBookingCheckParam();
        cbPreBookingCheckParam.setHotelId(hotelId);
        cbPreBookingCheckParam.setRoomId(roomId);
        cbPreBookingCheckParam.setRateplanId(ratePlanId);
        cbPreBookingCheckParam.setCheckIn(checkIn);
        cbPreBookingCheckParam.setCheckOut(checkOut);
        cbPreBookingCheckParam.setRoomCount(roomCount);
        cbPreBookingCheckParam.setCurrency(currency);
        cbPreBookingCheckParam.setOrderAmount(orderAmount);
        CNResponse<CbPreBookingCheckData> cnResponse = cnBookingService.preBookingCheck(cbPreBookingCheckParam);
        return AjaxResponseBody.success(cnResponse);
    }

    @ApiOperation("CNBooking预订下单")
    @PostMapping("/booking")
    public AjaxResponseBody booking(@Valid CbBookingParam cbBookingParam) {
        CbBookInfo cbBookInfo = new CbBookInfo();
        cbBookInfo.setBookName("预订人姓名");
        cbBookInfo.setBookPhone("15355462520");

        CbGuestInfos cbGuestInfos = new CbGuestInfos();
        List<CbGuestInfo> list = new ArrayList<>();
        CbGuestInfo guestInfo = new CbGuestInfo();
        guestInfo.setGuestName("入住人姓名");
        guestInfo.setGuestPhone("15355462521");
//        guestInfo.setCardNum("1111");
//        guestInfo.setCardTypeId("222");
//        guestInfo.setGuestFax("12345678");
//        guestInfo.setGuestType("444");
//        list.add(guestInfo);
//        cbGuestInfos.setGuestInfos(list);
        // cbBookingParam.setGuestInfos(cbGuestInfos);
        cbBookingParam.setGuestInfo(guestInfo);

        cbBookingParam.setBookInfo(cbBookInfo);
        cbBookingParam.setHotelId("209968");
        cbBookingParam.setRoomId("897381");
        cbBookingParam.setRateplanId("21797");
        cbBookingParam.setRoomCount(1);
        cbBookingParam.setCheckIn("2019-10-15");
        cbBookingParam.setCheckOut("2019-10-16");
        cbBookingParam.setCurrency("CNY");
        cbBookingParam.setOrderAmount("210");
        cbBookingParam.setCustomerOrderId(DateUtils.nowToYMDHMSStr());

        CNResponse<CbBookingData> cnResponse = cnBookingService.booking(cbBookingParam);
        return AjaxResponseBody.success(cnResponse);
    }

    /**
     * 组装校验参数
     * @param cbBookingParam
     * @return
     */
    private CbPreBookingCheckParam getCbPreBookingCheckParam(CbBookingParam cbBookingParam){
        CbPreBookingCheckParam cbPreBookingCheckParam = new CbPreBookingCheckParam();
        cbPreBookingCheckParam.setHotelId(cbBookingParam.getHotelId());
        cbPreBookingCheckParam.setRoomId(cbBookingParam.getRoomId());
        cbPreBookingCheckParam.setRateplanId(cbBookingParam.getRateplanId());
        cbPreBookingCheckParam.setCheckIn(cbBookingParam.getCheckIn());
        cbPreBookingCheckParam.setCheckOut(cbBookingParam.getCheckOut());
        cbPreBookingCheckParam.setRoomCount(String.valueOf(cbBookingParam.getRoomCount()));
        cbPreBookingCheckParam.setCurrency(cbBookingParam.getCurrency());
        cbPreBookingCheckParam.setOrderAmount(cbBookingParam.getOrderAmount());
        return  cbPreBookingCheckParam;
    }

    @ApiOperation("CNBooking订单搜索")
    @PostMapping("/orderSearch")
    public AjaxResponseBody orderSearch(String  orderId) {
        CbOrderSearchParam cbOrderSearchParam = new CbOrderSearchParam();
        cbOrderSearchParam.setOrderId(orderId);
        CNResponse<CbOrderSearchData> cnResponse = cnBookingService.orderSearch(cbOrderSearchParam);
        return AjaxResponseBody.success(cnResponse);
    }


    @ApiOperation("价格计划查询")
    @PostMapping("/plan/search")
    public AjaxResponseBody ratePlanSearch(@Validated CbRatePlanSearchParam param,
                                           @RequestParam(value = "countryId",defaultValue = "0001") String countryId,
                                           @RequestParam(value = "hotelId", required = true) String hotelId,
                                           @RequestParam(value = "roomId", required = false) String roomId,
                                           @RequestParam(value = "ratePlanId", required = false) String ratePlanId,
                                           @RequestParam(value = "checkIn", required = true) String checkIn,
                                           @RequestParam(value = "checkOut", required = true) String checkOut) {
        param.setCountryId(countryId);
        param.setHotelId(hotelId);
        if(!StringUtils.isEmpty(roomId)){
            param.setRoomId(roomId);
        }
        if(!StringUtils.isEmpty(ratePlanId)){
            param.setRatePlanId(ratePlanId);
        }
        CbHotelListSearchStayDateRange range = new CbHotelListSearchStayDateRange();
        range.setCheckIn(checkIn);
        range.setCheckOut(checkOut);
        param.setStayDateRange(range);
        CNResponse<CbRatePlanSearchData> cnResponse = cnBookingService.ratePlanSearch(param);
        return AjaxResponseBody.success(cnResponse);
    }

    private CbHotelListSearchParam getCbHotelListSearchParam() {
        CbHotelListSearchParam hotelSearchParam = new CbHotelListSearchParam();
        hotelSearchParam.setCityId("1201");
//        hotelSearchParam.setHotelName("西湖");
        hotelSearchParam.setLonAndLat("120.4342287385,30.237791384941");
        hotelSearchParam.setDistance("20");
        Date date = new Date();
        String checkIn = DateUtil.format(date, DatePattern.NORM_DATE_PATTERN);
        String checkOut = DateUtil.format(DateUtil.offsetDay(date, 1), DatePattern.NORM_DATE_PATTERN);
        hotelSearchParam.getStayDateRange().setCheckIn(checkIn);
        hotelSearchParam.getStayDateRange().setCheckOut(checkOut);
        hotelSearchParam.setPageSize(10);
        return hotelSearchParam;
    }

    @ApiOperation("地址查询")
    @PostMapping("/address/search")
    public AjaxResponseBody getAddressInCNBooking(CbAddressSearchParam param){

        CNResponse<CbAddressSearchData> cnResponse = cnBookingService.addressSearch(param);
        return AjaxResponseBody.success(cnResponse);
    }

    @ApiOperation("房间搜索测试")
    @PostMapping("/room")
    public AjaxResponseBody roomSearch(String countryId,
                                       String provinceId,
                                       String cityId,
                                       Integer pageSize,
                                       Integer pageNo){

        CbRoomSearchParam param = new CbRoomSearchParam();
        param.setCountryId(countryId);
        param.setProvinceId(provinceId);
        param.setCityId(cityId);
        param.setPageNo(pageNo);
        param.setPageSize(pageSize);
        CNResponse<CbRoomSearchData> cbRoomSearchDataCNResponse = cnBookingService.roomSearch(param);
        return AjaxResponseBody.success(cbRoomSearchDataCNResponse);
    }
}
